<?php
include_once "authcode.php";
session_start();
class Captcha{
    /* *
     * 输出验证码并把验证码的值保存的session中
     */
    public function my_code(){
        $image = imagecreatetruecolor(150, 50);
        //将背景设置为白色的
        $bgcolor = imagecolorallocate($image, 255, 255, 255);
        //将白色铺满地图
        imagefill($image, 0, 0, $bgcolor);

        //红色标记的数字
        $captch_code='';

        //随机数字数组
        for ($i=0; $i < 10; $i++) {
            $fontcontent[] = rand(0,9);
        }
        //echo implode('',$fontcontent);
        //随机取标记数字下标
        $num = rand(3,5);//标记数字的数量+1
        $sign = $this->my_number($num);
        $colourSign = $this->colour();//标记颜色

        foreach ($fontcontent as $k=>$v){
            $fontsize=10;//字体大小
            if(in_array($k,$sign)){
                $fontcolor=imagecolorallocate($image,$colourSign['data'][0],$colourSign['data'][1],$colourSign['data'][2]);
                $captch_code .= $v;
            }else{
                $other = $this->colour($colourSign['sign']);
                $fontcolor=imagecolorallocate($image,$other['data'][0],$other['data'][1],$other['data'][2]);
            }
            //数字的位置，0，0是左上角。不能重合显示不完全
            $x=($k*150/10);
            $y=5;
            imagestring($image,$fontsize,$x,$y,$v,$fontcolor);
        }

        //写入文字提示
        $chinese='请输入'.$colourSign['data'][3].'的数字';
        $chinese_len=mb_strlen($chinese);
        $chinese_other = $this->colour($colourSign['sign']);
        for($c=0;$c<$chinese_len;$c++){
            $chinese_fontsize=10;
            $word=mb_substr($chinese,$c,1);
            if($c == 3 || $c == 4){
                $chinese_fontcolor=imagecolorallocate($image,$colourSign['data'][0],$colourSign['data'][1],$colourSign['data'][2]);
            }else{
                $chinese_fontcolor=imagecolorallocate($image,$chinese_other['data'][0],$chinese_other['data'][1],$chinese_other['data'][2]);
            }
            $chinese_x=($c*150/$chinese_len)+5;
            $chinese_y = 42;
            //字体一定要绝对路径
            imagettftext($image, $chinese_fontsize, rand(20, 50), $chinese_x, $chinese_y, $chinese_fontcolor, __DIR__."/yzm.otf", $word);
        }

        $_SESSION['authcode'] = $this->authcode($captch_code);//保存验证码的结果

        //header('content-type:image/png');
        //imagepng($image);
        header('content-type:image/jpeg');
        imagejpeg($image);
        //销毁
        imagedestroy($image);
    }

    /*
     * 验证码加解密
     * $str 需要加解密的字符串
     * $state 加解密状态  E 加密  D 解密
     * $expiry 加密字符串有效时长  0为永久有效
     * $len 随机字符串  取值 0-32
     * return 成功返回字符串  失败返回false
     * */
    public function authcode($str,$state='E',$expiry=90,$len=6){
        $authcode=new authcode($len,$expiry);
        $flag = $authcode->auth_code($str,$state);
        if($flag) return $flag;
        else return false;
    }

    /*
     * 验证验证码
     * */
    public function check($str){
        $old = $_SESSION['authcode'];
        $flag=self::authcode($old,'D');
        if(!$flag) return ['code'=>404,'msg'=>'验证码过期或错误'];
        if($flag != $str) return ['code'=>404,'msg'=>'验证码错误'];
        else return ['code'=>200,'msg'=>'成功'];
    }

    //获取颜色
    public function colour($num=''){
        $data=[
            ['255','0','0','红色'],
            //['128','0','128','紫色'],
            ['0','0','255','蓝色'],
            ['0','255','0','绿色'],
            ['0','0','0','黑色'],
        ];
        if($num == 0 || $num > 0){
            unset($data[$num]);
            $data=array_merge($data);
        }
        return $this->my_random($data);
    }

    public function my_random($data){
        $c=count($data);
        $sign = rand(0,($c-1));
        return ['sign'=>$sign,'data'=>$data[$sign]];
    }

    //获取重复的随机数
    public function my_number($num){
        $arr=[];
        $data=[0,1,2,3,4,5,6,7,8,9];
        for($i=0;$i<=$num;$i++){
            $flag=rand(0,(count($data)-1));
            $arr[]=$data[$flag];
            unset($data[$flag]);
            $data=array_merge($data);
        }
        return $arr;
    }

    //生成验证码
    public function entry(){
        //$colourSign=$this->colour();
        $this->my_code();
    }

}
